Previous Page

nihilist@mainpc - 2024-05-14

Haveno DEX Direct Fiat to Monero transactions

TODO: need context (private / anonymous use)

In this tutorial we're going to cover how to do a Fiat to Monero trade from the brand new (and long awaited!) Haveno Decentralised Exchange, using the Face-to-Face (F2F) payment method.

Sidenote: i don't recommend face-to-face as a payment option of choice, this is just to try out how a basic trade Haveno DEX works!

Before reading through this tutorial, make sure you understand why Decentralised Exchanges are the next step in Decentralised Finances in this blogpost i previously made, so that you have all the context.

As we are covering a DEX (Decentralised Exchange), it means we are not covering how to use a website onto which you are purchasing monero (like the now defunct Localmonero (RIP)), we are covering a software that you install on your computer (hence the Decentralisation in "DEX"), to trade Peer to Peer (P2P) with the other users.

The resilliency of Haveno is on multiple levels: First of all the more Seed nodes there are, the harder to take down the Haveno network is. The anonymity provided by the Tor network of Haveno for all nodes (which is on by default), also adds up to the resiliency.

Clientside, the more peers (users) there are, the more diverse and bigger the exchange will be, and so will the decentralised market be at large. The sooner the Monero market moves to Decentralised Exchanges, the more unstoppable it will become.

Lastly if the Haveno network is completely taken down (let's say if all the seed nodes are taken down somehow), all that's left is for another administrator to spin up a new haveno network since the code is all open source, to repeat the cycle again.

You can check out my quick coverage of Haveno DEX on Monero Topia here. (Definitely check out MoneroTopia for the latest news in the Monero world, awesome show!)

DISCLAIMER: THERE ARE NO OFFICIAL HAVENO NETWORK INSTANCES, THERE ARE ONLY THIRD PARTY HAVENO NETWORKS LIKE HAVENO RETO.

IF YOU SEE A HAVENO CLAIM TO BE THE OFFICIAL NETWORK LIKE THIS ONE, DONT FALL FOR THEIR SCAM!

OPSEC Recommendations:

  1. Hardware : (Personal Computer / Laptop)

  2. Host OS: Linux

  3. Hypervisor: libvirtd QEMU/KVM

  4. Virtual Machine: Linux or Whonix or Tails

I recommend using this setup into one of the above mentionned VMs, either for Private use, or Anonymous use, as per the 4 basic OPSEC levels. (Note that Deanonymization will happen during the Fiat transaction, but it is minimized as you're revealing your identity to an other peer, rather than to a centralised exchange)

How to install Haveno ?

First, we need to find a Haveno Network, Haveno Reto being one of the first ones to show up, we're going to try them out:

Let's get the Haveno binaries from Reto's github repository, (which was forked from the original Haveno repository, maintained by Woodser)

For Debian Users

Here, we are on a debian machine, so we download the ubuntu package (which contains the .deb and .rpm file)

For Arch Linux Users

You can either extract the .rpm (which is originally intended for Fedora users) package and run the haveno binary yourself, or use the AUR package maintained by duje

For Windows Users

If you are a windows user (know that it cant be trusted as it's not an open source operating system, check out my tutorial here on how to install linux instead), if you're too lazy you can check out darknetreporter's tutorial:

For Debian Users

Back on Debian (note: these instructions are the same if you are on Whonix!), the zip package is downloaded:

Then unpack the zipfile wherever you want:


[ mainpc ] [ /dev/pts/5 ] [~]
→ unzip ~/Downloads/HavenoInstaller-ubuntu-latest.zip -d ~/Documents/
Archive:  /home/nihilist/Downloads/HavenoInstaller-ubuntu-latest.zip
  inflating: /home/nihilist/Documents/desktop-1.0.3-SNAPSHOT-all.jar.SHA-256
  inflating: /home/nihilist/Documents/haveno-1.0.3-1.x86_64.rpm
  inflating: /home/nihilist/Documents/haveno_1.0.3-1_amd64.deb

[ mainpc ] [ /dev/pts/5 ] [~]
→ cd ~/Documents/haveno-reto

[ mainpc ] [ /dev/pts/5 ] [~/Documents/haveno-reto]
→ ls
desktop-1.0.3-SNAPSHOT-all.jar.SHA-256  haveno_1.0.3-1_amd64.deb  haveno-1.0.3-1.x86_64.rpm

Here since we are currently on a debian machine, we're going to use the .deb file to install haveno, as follows:


[ mainpc ] [ /dev/pts/1 ] [~/Documents/haveno-reto]
→ sudo dpkg -i haveno_1.0.3-1_amd64.deb
[sudo] password for nihilist:
Selecting previously unselected package haveno.
(Reading database ... 214512 files and directories currently installed.)
Preparing to unpack haveno_1.0.3-1_amd64.deb ...
Unpacking haveno (1.0.3-1) ...
Setting up haveno (1.0.3-1) ...

#if it fails, run "apt install -f" to install the missing dependencies and then dpkg -i haveno.deb again.

If you previously used haveno, make sure you delete the folder in ~/.local/share/Haveno-reto as follows, to clear up all the previous wallet infos


[ mainpc ] [ /dev/pts/1 ] [~/Documents/haveno-reto]
→ rm -rf ~/.local/share/Haveno-reto

if you want to see the haveno logs from the CLI as you use it, you can do as follows:


[ mainpc ] [ /dev/pts/6 ] [~/Nextcloud/blog]
→ cd ~/.local/share/Haveno-reto

[ mainpc ] [ /dev/pts/6 ] [.local/share/Haveno-reto]
→ ls
haveno.log  haveno.properties  monerod  monero-wallet-rpc  monero-wallet-rpc.log  version  xmr_mainnet

[ mainpc ] [ /dev/pts/6 ] [.local/share/Haveno-reto]
→ tail -f haveno.log
May-29 20:55:23.829 [pool-16-thread-5] INFO  h.c.t.TaskRunner: Run task: SendOfferAvailabilityRequest
May-29 20:55:23.830 [pool-16-thread-5] INFO  h.c.o.a.t.SendOfferAvailabilityRequest: Send OfferAvailabilityRequest with offerId mqbtqDh-1ec9fa64-e5e7-4766-9936-519951bc5f36-106 and uid d85caa9c-840c-45eb-8642-4cb12828fc93 to peer rlrsc6nfqbvqhly3qjcb36qzvw44xnxqhcht3nqndy324ewg4dut4iqd.onion:9999
May-29 20:55:23.930 [JavaFX Application Thread] INFO  h.c.o.a.t.SendOfferAvailabilityRequest: OfferAvailabilityRequest arrived at peer: offerId=mqbtqDh-1ec9fa64-e5e7-4766-9936-519951bc5f36-106; uid=d85caa9c-840c-45eb-8642-4cb12828fc93
May-29 20:55:25.292 [JavaFX Application Thread] INFO  h.d.c.c.c.PopOver: hide:200.0 ms
May-29 20:55:25.903 [pool-48-thread-1] INFO  h.c.o.a.OfferAvailabilityProtocol: Received OfferAvailabilityResponse from rlrsc6nfqbvqhly3qjcb36qzvw44xnxqhcht3nqndy324ewg4dut4iqd.onion:9999 with offerId mqbtqDh-1ec9fa64-e5e7-4766-9936-519951bc5f36-106 and uid 986ee04a-47d2-4303-a9fc-12d18cc158ce
May-29 20:55:25.905 [pool-48-thread-1] INFO  h.c.t.TaskRunner: Run task: ProcessOfferAvailabilityResponse
May-29 20:55:25.905 [pool-48-thread-1] INFO  h.c.o.a.OfferAvailabilityProtocol: Send AckMessage for OfferAvailabilityResponse to peer rlrsc6nfqbvqhly3qjcb36qzvw44xnxqhcht3nqndy324ewg4dut4iqd.onion:9999 with offerId mqbtqDh-1ec9fa64-e5e7-4766-9936-519951bc5f36-106 and sourceUid 986ee04a-47d2-4303-a9fc-12d18cc158ce
May-29 20:55:25.907 [JavaFX Application Thread] INFO  h.c.o.a.OfferAvailabilityProtocol: AckMessage for OfferAvailabilityResponse arrived at makersNodeAddress rlrsc6nfqbvqhly3qjcb36qzvw44xnxqhcht3nqndy324ewg4dut4iqd.onion:9999. offerId=mqbtqDh-1ec9fa64-e5e7-4766-9936-519951bc5f36-106, sourceUid=986ee04a-47d2-4303-a9fc-12d18cc158ce
May-29 20:55:26.108 [pool-48-thread-1] INFO  h.c.o.OpenOfferManager: Received AckMessage for OfferAvailabilityRequest with offerId mqbtqDh-1ec9fa64-e5e7-4766-9936-519951bc5f36-106 and uid d85caa9c-840c-45eb-8642-4cb12828fc93
May-29 20:55:27.427 [JavaFX Application Thread] INFO  h.d.c.c.c.PopOver: hide:200.0 ms

next just launch Haveno as it should have been added to your system:

For Whonix Users: use tor bridges to make Haveno connect!

Next, haveno is going to connect to Tor. WHONIX USERS: If it is facing issues connecting wait for the client to ask you to set the tor settings:

then just get a torbridge from torproject.org:

and add them inside haveno, and restart it:

Then it should connect just fine:

you may need to wait a bit for your haveno node to sync up initially: (probably 1-2 minutes)

and once it finishes synchronising, you're in Haveno!

For Tails OS Users: Use BrandyJson's Script!

If you want to have a TailsOS VM running, check out my latest tutorial on it here.

Download the latest haveno package just like on debian, then put it in the persistant storage:


amnesia@amnesia:~$ mv ~/Tor\ Browser/haveno_1.0.7-1_amd64.zip ~/Persistent/
amnesia@amnesia:~$ cd Persistent/
amnesia@amnesia:~/Persistent$ ls -lash
total 266M
4.0K drwx------  3 amnesia amnesia 4.0K Jun 14 09:58  .
   0 drwx------ 24 amnesia amnesia  600 Jun 14 09:19  ..
266M -rw-r--r--  1 amnesia amnesia 266M Jun 14 09:57  haveno_1.0.7-1_amd64.zip

amnesia@amnesia:~/Persistent$ sudo apt install unzip

amnesia@amnesia:~/Persistent$ unzip haveno_1.0.7-1_amd64.zip 
Archive:  haveno_1.0.7-1_amd64.zip
  inflating: desktop-1.0.7-SNAPSHOT-all.jar.SHA-256  
  inflating: haveno_1.0.7-1_amd64.deb  

Then we can use BrandyJson's script to install haveno on tails:


amnesia@amnesia:~/Persistent$ wget https://raw.githubusercontent.com/BrandyJSon/haveno-install-tails/main/haveno-install.sh
--2024-06-14 10:29:07--  https://raw.githubusercontent.com/BrandyJSon/haveno-install-tails/main/haveno-install.sh
Resolving raw.githubusercontent.com (raw.githubusercontent.com)... 185.199.111.133
Connecting to raw.githubusercontent.com (raw.githubusercontent.com)|185.199.111.133|:443... connected.
HTTP request sent, awaiting response... 200 OK
Length: 3393 (3.3K) [text/plain]
Saving to: \u2018haveno-install.sh\u2019

haveno-install.sh                                    100%[=====================================================================================================================>]   3.31K  14.3KB/s    in 0.2s    

2024-06-14 10:29:09 (14.3 KB/s) - \u2018haveno-install.sh\u2019 saved [3393/3393]

amnesia@amnesia:~/Persistent$ vim haveno-install.sh  #review the script, and change the dpkg -i line with the correct haveno version if it has changed

Be aware that this is not an official way of installing haveno on Tails, it's going barbaric on apparmor and the security model of tails, later on, there will be a better way to install haveno on Tails OS


#if the bashscript contains '\r' characters , do the following:
amnesia@amnesia:~/Persistent$ tr -d '\r' < haveno-install.sh  > haveno-install.sh

#then install it:
amnesia@amnesia:~/Persistent$ sudo bash haveno-install.sh 
[sudo] password for amnesia:          

Selecting previously unselected package haveno.
(Reading database ... 148641 files and directories currently installed.)
Preparing to unpack .../haveno_1.0.7-1_amd64.deb ...
Unpacking haveno (1.0.7-1) ...
Setting up haveno (1.0.7-1) ...
Allowing amnesia to read tor control port cookie, only run this script when you actually want to use haveno

!!! not secure !!!

Updating apparmor-profile
Adding rule to iptables to allow for monero-wallet-rpc to work
Updating torsocks to allow for inbound connection
Restarting onion-grater service
Everything is set up just run

source ~/.bashrc

Then you can start haveno using haveno-tails

amnesia@amnesia:~/Persistent$ source ~/.bashrc
amnesia@amnesia:~/Persistent$ haveno-tails
Jun-14 10:52:51.099 [main] INFO  haveno.common.util.Utilities: System info: os.name=Linux; os.version=6.1.0-21-amd64; os.arch=amd64; sun.arch.data.model=64; JRE=21.0.2+14-LTS (BellSoft); JVM=21.0.2+14-LTS (OpenJDK 64-Bit Server VM) 
Jun-14 10:52:51.120 [main] INFO  haveno.common.app.AsciiLogo: 

                                                                                                              
                                                                                                              
                                                                                                              
                                                   0X                                                         
                                              OOdolcck                                                        
                                       KXKNN0occcccccck:   :Kxxk0d                                            
                                     klccccccccccccccccck0xcccccccxK'                                         
                                    xccccccccccccccclOKKOocccccccccclxK                                       
                                  .xccccccccccccccclWMMMMMd:::::::::ccco                                      
                                 'dccccccc:::cccccclWMMMMMo:::::::::::cc;                                     
                                ,occccc:::::::::::::cxO0kl:::::::::::::cd                                     
                               ;occccc:::::cddddddc;;;;;;;;:ddddddl:::::coldOK                                
                              :occccc::::::xMMMMMMo,,,,,,,,cMMMMMMk::::::cccccoOc                             
                             llccccc:::::;;dMMMMMMo,,,,,,,,cMMMMMMk:::::::cccccc,                             
                             'cccccc::::;,,dMMMMMMl'''''',,cMMMMMMk::::::::ccccc.                             
                             .cccccc::::,,,dMMMMMMo'''''',,cMMMMMMk::::::::ccccc                              
                              :ccccc:::::;;dMMMMMM0xxxxxxxxOMMMMMMk::::::::ccc'                               
                              ;ccccc:::::::xMMMMMMMMMMMMMMMMMMMMMMk::::::ccccco                               
                              'ccccc:::::::xMMMMMMMMMMMMMMMMMMMMMMk:::::ccccccco                              
                              .ccccccc:::::xMMMMMMd::::::::oMMMMMMk:::::ccccccc                               
                               :cccccccc:::xMMMMMMo,,,,,,,,cMMMMMMk:::::cccccc                                
                                cccccccccc:xMMMMMMo,,,,,,,,cMMMMMMk::::cccccc                                 
                                :ccccccccccxMMMMMMo,,,,,,,,cMMMMMMO:cccccccc                                  
                                 ccccccccccxMMMMMMd;;;;;;;:lMMMMMMOcccccccc                                   
                                    ccccccclooooooc::::::::cddddddlcccccc:                                    
                                      .ccccc::::::::::::::ccccccccccccccc                                     
                                         :cccc:::::::::::ccccccccccccc                                        
                                           .cccc:::::::ccccccccccc,                                           
                                              'ccccccccccccc.                                                 
                                                  ;ccccc:                                                     
                                                                                                              
                                                                                                              
                                                                                                              
                                                                                                              
                 .XXX.   .XXX.    .XXXk  dXX0     ;XXX.KXXXXXX, xXX0     :XX0    ,XK000KK                     
                 .ccc.   .ccc.    xccccc  ;cco   .occ. ccccccc. :cccdo   ;cc:  oxlccccccco0.                  
                 .ccc.   .ccc.   dcc'ccl.  :ccl  dcc.  ccc'     :cccccO. ;cc: lccc      'ccd                  
                 .ccclllllccc.  ccc: .ccx  .ccl,dcc'   cccllll. :cc, ccox;cc: :cc:      .ccc.                 
                 .ccc     ccc. 'lccl0kcccd  .cclcc,    ccc.     :cc;  .ccocc: .ccco     kcc:                  
                 .ccc.   .ccc. dcc.    :ccl  .ccc;     cccd000' :cc;    cccc:   cccxO0kocc,                   
                                                                                   :ccc.        

Fiat for Monero, Face to Face Trade



First step is to setup your account for Face to Face Trades:

Here we specify that we want to do face to face trades in Berlin (Germany) as an example, we will use our FIAT currency, Euros (in cash), you can also specify alternative ways to get contacted if you don't like the built in chat in Haveno DEX, such as email or phone number, etc. Then hit the "save new account" button:

Make sure you read carefully what a face-to-face fiat->XMR trade is, and what are it's risks, if you're fine with it, click "i understand". Now that your account is created, head over to the "Buy" section, as you want to buy monero:

Then you can publish a Fiat->XMR face to face trade offer like so:

So here we want to purchase 0.10 XMR, for the current market price, which amounts to 12 euros. then hit next step:

Now here is when we get introduced to the trade protocol's security deposit system as detailed in the Haveno FAQ. I'll make a simple diagram to explain the situation:


Quote from Haveno's FAQ: (https://haveno.exchange/faq/#what-are-the-differences-in-the-trade-protocol) 

[...]

Bisq recently adopted a protocol based on 2/2 multisig, while Haveno will use their previous protocol: 2/3 multisignature. In a 2/3 multisignature trade, each trader owns one key; this key will be paired with the key of the other trader and will be used to unlock funds and deposits. It’s a 2 of 3 (2/3) protocol because you need only two out of three keys to move funds from the multisignature wallet.

If everything goes fine, the two traders will use their keys to complete the transfer process. If something goes wrong, one of the two parties won’t use their key to complete the transaction, and this is where the arbitrator comes to action.

Arbitrators are inherited from Bisq’s 2/3 protocol. They are a trusted role and have the duty of releasing the funds to one of the two parties in case of a conflict. To do so, they use the third key of the 2/3 multisig protocol.

[...]

To make it short, you (Bob) in this case, want to trade Fiat, for Alice's XMR, in person. BOTH you and Alice need to put in some monero into the trade, as a security deposit. That is so in case if you try to scam Alice, you will loose something in the process, preventing you from trying to repeatedly scam people, and vice versa.

Due to the 2/3 multisig nature of the trade, there needs to be at least 2 agreeing parties to complete the trade. If all goes well, you and Alice agree on the trade, and the security deposit monero is released. If not, the Arbitrator will step in to punish the wrongdoer (by not giving him the security deposit back), and give the security deposit to the honest party.

The following example will cover a successful trade between you and Alice. If you want to see a trade dispute, check out this tutorial.

So here, you need to send the security deposit to be able to post your buying offer, just send it from your monero wallet like so:

Once you've sent the monero to your haveno trade for the security deposit, you need to wait approx 20 minutes for the transaction to be confirmed by the network

Approx 20 mins later, the trade shows up as enabled:

Bob: puts 0.1005 XMR into the trade for the security deposit,

You (and the other haveno peers) can see it from the Sell tab:

Here you just need to wait for someone to accept the trade. Once they do, they will need to send their share of the security deposit too just like we previously did. Once they do it will show up on your end as an initiated trade:

Alice puts 0.1005 XMR into the trade for the security deposit. Then the trade is secured

Same as before, you need to wait for the security deposit to be validated by the network (approx 20 mins again). In the meantime you can chat with the trader by clicking the "Open Trader Chat" button.

Once the security deposit has been validated by the network for the other party, you will get a notification that the trade can begin:

Next step is for you to go and give the 12 Euros to Alice, and once you do, you confirm that the Payment has been sent like so:

Then, you wait for Alice to confirm that she has recieved the 12 Euros (it will show up as "Peer confirmed message receipt"):

Alice can then send the 0.10 XMR to Bob, after Bob Pays her in Euros.

Then here, you just wait for the Monero to arrive in your Haveno monero wallet, it will first show up as Pending on the top right corner:

Wait another 20 minutes for the transaction to be validated by the network, and it will show up in your Haveno monero wallet as Available balance:

The trade is successful, the security deposit is now released, Bob gets his 0.1005 XMR back, and Alice too. (minus the transcation fees and arbitrator fees)

And that's it, you can now pop the Champagne as you completed your first Fiat -> XMR transaction on a Decentralised exchange! 🥂

Withdrawing your Monero from Haveno to another Wallet



Now all that's left is to withdraw your monero from your Haveno monero wallet to your other Monero Wallet:

Head over to Funds > send funds, tick the "Amounts includes mining fee" option, and select the amount of monero you want to withdraw, in this case i'm withdrawing all of it.

Then confirm that you want to withdraw the funds, and check your monero wallet for the incoming transaction:

And that's it! you just withdrew your funds to your other monero wallet!

Check out my other tutorials on Decentralised Finances below:

  1. ✅ How to acquire and use Monero
  2. ✅ Haveno Decentralised Exchange direct Fiat -> XMR transaction ⭐
  3. ✅ Haveno DEX Dispute resolution (Fiat -> XMR)
  4. ✅ Haveno DEX Bank Transfer (ex: SEPA) -> XMR transaction
  5. ✅ Haveno DEX Cash By Mail -> XMR transaction ⭐

Nihilism

Until there is Nothing left.

About nihilist

Donate XMR: 8AUYjhQeG3D5aodJDtqG499N5jXXM71gYKD8LgSsFB9BUV1o7muLv3DXHoydRTK4SZaaUBq4EAUqpZHLrX2VZLH71Jrd9k8


Contact: nihilist@nihilism.network (PGP)